import {
  delMenu,
  insertMenu,
  MenuApi,
  modifyMenu,
} from '@/api/userCenter/system/menu'
import { MenuItem, MenuLevel } from '@/api/userCenter/system/model/menuModel'
import { iconNameList } from '@/components/registerAntdIcons'
import store from '@/store'
import { message } from 'ant-design-vue'
import { cloneDeep } from 'lodash-es'
import { computed, nextTick, reactive, ref } from 'vue'
import { EditDialogFormState, EditDialogState } from '../types'

const useOperateMenu = (searchApi: () => Promise<void>) => {
  const editDialogFormRef = ref()
  /**
   * 编辑弹框内的表单的一些属性
   */
  const editDialogFormBind = reactive({
    labelCol: {
      span: 5,
    },
    wrapperCol: {
      span: 16,
    },
  })
  /**
   * 支持的图标列表
   */
  const editDialogIconOptions = ref(
    iconNameList.map((icon) => {
      return {
        name: icon,
      }
    })
  )
  /**
   * 表单初始化数据
   */
  const initEditDialogFormState: EditDialogFormState = {
    id: '',
    pid: '',
    level: MenuLevel.MENU,
    code: '',
    name: '',
    icon: '',
    path: '',
    enabled: true,
  }
  /**
   * 编辑弹框相关状态
   */
  const editDialogState = reactive<EditDialogState>({
    visible: false,
    title: '添加菜单',
    action: 'add',
    formState: cloneDeep(initEditDialogFormState),
  })
  /**
   * 是否是按钮类型
   */
  const isButtonType = computed(
    () => editDialogState.formState.level === MenuLevel.BUTTON
  )
  /**
   * 是否时页面类型
   */
  const isPageType = computed(
    () => editDialogState.formState.level === MenuLevel.PAGE
  )
  /**
   * 根据不同的level获取不同名称
   */
  const BtoMText = computed(() => {
    switch (editDialogState.formState.level) {
      case MenuLevel.APP:
        return '应用'
      case MenuLevel.MENU:
        return '菜单'
      case MenuLevel.BUTTON:
        return '按钮'
      case MenuLevel.PAGE:
        return '页面'
      default:
        return '未知'
    }
  })

  /**
   * 打开添加框
   *
   * @param pid
   * @param level
   */
  const addMenu = async (pid: string, level: MenuLevel = MenuLevel.MENU) => {
    editDialogState.action = 'add'
    editDialogState.visible = true
    editDialogState.title = '添加菜单'
    await nextTick()
    editDialogState.formState = { ...initEditDialogFormState, level, pid }
    console.log(editDialogState.formState)
    editDialogFormRef.value.resetFields()
  }

  /**
   * 打开编辑框
   * @param menuItem
   */
  const editMenu = (menuItem: MenuItem) => {
    editDialogState.action = 'edit'
    editDialogState.visible = true
    editDialogState.title = '编辑菜单'
    // eslint-disable-next-line @typescript-eslint/no-unused-vars
    const { children, updateTime, createTime, ...rest } = cloneDeep(menuItem)
    editDialogState.formState = rest
  }

  /**
   * 切换level时清除一些不必要的数据
   */
  const onMenuTypeChange = () => {
    const { level, pid } = editDialogState.formState
    editDialogState.formState = { ...initEditDialogFormState, level, pid }
  }

  /**
   * 删除指定菜单
   * @param menuItem
   */
  const deleteMenu = async (menuItem: MenuItem) => {
    await delMenu({ id: menuItem.id })
    message.success('删除成功！')
    await searchApi()
  }

  /**
   * 确认编辑或者添加菜单
   */
  const handleOk = async () => {
    if (editDialogState.action === 'add') {
      // eslint-disable-next-line @typescript-eslint/no-unused-vars
      const { enabled, id, ...reqData } = editDialogState.formState
      await insertMenu(reqData)
      message.success('添加成功！')
    } else {
      await modifyMenu(editDialogState.formState)
      message.success('编辑成功！')
    }
    editDialogState.visible = false
    await searchApi()
  }
  const insertMenuLoading = computed(() =>
    store.getters['global/isOpLoading'](MenuApi.INSERT_MENU)
  )
  const modifyMenuLoading = computed(() =>
    store.getters['global/isOpLoading'](MenuApi.MODIFY_MENU)
  )

  return {
    initEditDialogFormState,
    editDialogState,
    addMenu,
    editDialogFormRef,
    editDialogFormBind,
    editDialogIconOptions,
    editMenu,
    isButtonType,
    isPageType,
    BtoMText,
    handleOk,
    insertMenuLoading,
    modifyMenuLoading,
    deleteMenu,
    onMenuTypeChange,
  }
}

export default useOperateMenu
